FireLens(Fluent Bit)コンテナが Key has an empty value で起動できないときの原因と対処方法
FireLens(Fluent Bit)コンテナがKey has an empty value
のエラーで起動しない状況を調査する機会がありました。同エラー発生時の切り分けの参考用にまとめておきます。
検証環境
項目 | バージョン |
---|---|
aws-for-fluent-bit | 2.17.0 |
Fluent Bit | 1.8.1 |
Fargate platform | 1.4.0 |
以下のブログポストで紹介されているCloudFormationのテンプレートで構築した環境です。
状況
タスクを実行すると停止理由がTask failed to startで、アプリケーションコンテナ(webapp)と、FireLensコンテナ(log_router)共にSTOPPEDで起動できませんでした。
FireLensコンテナ自身のログ保存先は、log driverの設定をawslogsに設定してあるためCloudWatch Logsに保存されてます。CloudWatch LogsからFireLensコンテナの起動時のログを確認してみます。
[ Error] Error in line 29: Key has an empty value
FireLensコンテナが起動に失敗するなんて、カスタムログルーティング用の設定ファイルにミスがあるのでは?と疑いたくなります。今回の検証環境ではカスタムログルーティングの設定はしていません。素のFireLensイメージ(aws-for-fluent-bit)なのに起動に失敗しています。
原因
Key has an empty value
とは、一体どこのKeyに対するValueが空と言っているのでしょうか。
アプリケーションコンテナのlog driverをawsfirelensに変更した後のオプションにKey=Name, Velue=""
のことでした。管理コンソールから手動でタスク定義を作成し、log driverをawslogsからfirelensに変更すると、デフォルトの初期値としてNameキーが空のまま残ります。手動で設定する場合は気をつけないと見落とすかもしれません。
タスク定義をJSONでみると以下の箇所です。
"logConfiguration": { "logDriver": "awsfirelens", "options": { "Name": "" } }, ...snip... "memoryReservation": null, "volumesFrom": [], "stopTimeout": null, "image": "public.ecr.aws/nginx/nginx:latest",
対処
空のNameキーを削除します。不要なキーを削除するこれだけです。
タスク定義をJSONからみるとこうなります。
"environmentFiles": [], "logConfiguration": { "logDriver": "awsfirelens" }, "entryPoint": [],
Nameキー以外が空だったら?
NameキーをTestに変更し、値は空にしてタスク定義を作成しタスクを実行してみます。
停止理由は見切れていますが、Nameキーが空ときとは異なり停止理由に説明があります。ちなみにlog_routerのコンテナは起動すらしていないため、CloudWatch Logsにログが一切記録されていませんでした。キー名の違いにより挙動が異なることはわかりました。
停止理由が見切れるためAWS CLIから確認してみます。停止したタスクIDが欲しいので停止したもの一覧を出力します。
aws ecs list-tasks \ --cluster minimum-test-cluster \ --desired-status STOPPED
{ "taskArns": [ "arn:aws:ecs:ap-northeast-1:123456789012:task/minimum-test-cluster/049feed3cea24451b2ae3803b8955b20", "arn:aws:ecs:ap-northeast-1:123456789012:task/minimum-test-cluster/0b35e9af59e14f47bb7351a02f0b0e67" ] }
特定のタスクIDから停止理由のみフィルターしてメッセージを確認します。
aws ecs describe-tasks \ --cluster minimum-test-cluster \ --tasks arn:aws:ecs:ap-northeast-1:123456789012:task/minimum-test-cluster/049feed3cea24451b2ae3803b8955b20 \ --query 'tasks[0].stoppedReason'
結局メッセージ全文は確認できませんでした。
"InternalError: unable to generate fireLens config file: unable to generate fireLens config content: unable to generate fluent config output section: unable to apply log options of container webapp to fireLens config: missing output key Name which is re..."
おわりに
Fluent Bitや、FireLensというよりはECS Fargateのタスク定義の問題だったのですが、エラーメッセージの内容だけで特定するのはなかなか難しいですね。